#include "partie.h"

#include "moteurJeu.h"

Partie::Partie(MoteurJeu * parent, Joueur * jB, Joueur * jN) {
    this->parent = parent;

    this->jB = jB;
    this->jN = jN;

    initialiser();
}

void Partie::initialiser() {
    int i, j;

    for (i=0; i<8; i++) {
        for (j=0; j<8; j++) {
           this->matriceJeu[i][j] = NULL;
        }
    }

    /* Consctruction des pièces du jeu */
    /* Celle du joueur Blanc : */
    matriceJeu[0][0] = new Tour(this, 0, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[0][0]) ;

    matriceJeu[1][0] = new Cavalier(this, 1, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[1][0]) ;

    matriceJeu[2][0] = new Fou(this, 2, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[2][0]) ;

    matriceJeu[3][0] = new Reine(this, 3, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[3][0]);

    matriceJeu[4][0] = new Roi(this, 4, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[4][0]);

    matriceJeu[5][0] = new Fou(this, 5, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[5][0]);

    matriceJeu[6][0] = new Cavalier(this, 6, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[6][0]);

    matriceJeu[7][0] = new Tour(this, 7, 0, BLANC) ;
    listePieceJB.push_back(matriceJeu[7][0]);

    /* Ajout des pions blancs sur le plateau */
    for (i=0; i<8; i++) {
        matriceJeu[i][1] = new Pion(this, i, 1, BLANC);
        listePieceJB.push_back(matriceJeu[i][1]);
    }

    /* Celle du joueur Noir : */
    matriceJeu[0][7] = new Tour(this, 0, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[0][7]);

    matriceJeu[1][7] = new Cavalier(this, 1, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[1][7]);

    matriceJeu[2][7] = new Fou(this, 2, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[2][7]);

    matriceJeu[3][7] = new Reine(this, 3, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[3][7]);

    matriceJeu[4][7] = new Roi(this, 4, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[4][7]);

    matriceJeu[5][7] = new Fou(this, 5, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[5][7]);

    matriceJeu[6][7] = new Cavalier(this, 6, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[6][7]);

    matriceJeu[7][7] = new Tour(this, 7, 7, NOIR) ;
    listePieceJN.push_back(matriceJeu[7][7]);

    /* Ajout des pions noirs sur le plateau */
    for (i=0; i<8; i++) {
        matriceJeu[i][6] = new Pion(this, i, 6, NOIR);
        listePieceJN.push_back(matriceJeu[i][6]);
    }

    // Initialisation de la matrice de déplacement
    initialiserMatriceDepl();

    // Initalisation des variables d'historisation de coup
    this->piece_capturee_last = NULL ;
    this->piece_last = NULL ;
    this->x_last = -10 ;
    this->y_last = -10 ;

    // En passant
    enPassantX = -10;
    enPassantY = -10;

    // Roques
    roquePB = true;
    roqueGB = true;
    roquePN = true;
    roqueGN = true;

    // Coups
    nb_coups = 0;
    nb_demi_coups = 0;

    // Le joueur blanc débute
    this->joueurActu = BLANC;
    jB->debutTour();


    /*Message msg(ECHIQUIER_MODIFIE);
    parent->moteurGraphique->envoyerMessage(msg);*/
}

void Partie::deplacerPiece(Piece * p, int x_dest, int y_dest, bool simuler) {
    bool deplacementAutorise = false;
    bool en_passant_active = false;

    if (simuler) {
        // SAUVER ETAT
        sauvegarderEtat();
    }

    switch(matriceDepl[x_dest][y_dest]) {
        case DEPLACEMENT:
        case PROMOTION_DEPLACEMENT:
            this->piece_capturee_last = NULL;
            deplacementAutorise = true;

            if (matriceDepl[x_dest][y_dest]==PROMOTION_DEPLACEMENT && !simuler) {
                promotionX = x_dest;
                promotionY = y_dest;
                
                if (p->getCouleur()==BLANC)
                    jB->choixPromotion();
                else
                    jN->choixPromotion();
                
                parent->setAttentePromotion(true);
            }
            break;
        case DEPLACEMENT_DOUBLE:
            this->piece_capturee_last = NULL;
            this->enPassantX = x_dest;
            if (p->getCouleur()==BLANC)
                this->enPassantY = y_dest-1;
            else
                this->enPassantY = y_dest+1;

            en_passant_active = true;
            deplacementAutorise = true;
            break;
        case CAPTURE:
        case PROMOTION_CAPTURE:
            if (matriceJeu[x_dest][y_dest]->getCouleur() == NOIR)
                this->listePieceJN.remove(matriceJeu[x_dest][y_dest]);
            else
                this->listePieceJB.remove(matriceJeu[x_dest][y_dest]);

            enregistrerDernierePieceCapturee(matriceJeu[x_dest][y_dest], x_dest, y_dest);

            delete this->matriceJeu[x_dest][y_dest];
            this->matriceJeu[x_dest][y_dest] = NULL;

            deplacementAutorise = true;

            if (matriceDepl[x_dest][y_dest]==PROMOTION_CAPTURE && !simuler) {
                promotionX = x_dest;
                promotionY = y_dest;
                
                if (p->getCouleur()==BLANC)
                    jB->choixPromotion();
                else
                    jN->choixPromotion();
                
                parent->setAttentePromotion(true);
            }
            break;
        case EN_PASSANT:
            if (p->getCouleur() == BLANC) {
                this->listePieceJN.remove(matriceJeu[x_dest][y_dest-1]);
                enregistrerDernierePieceCapturee(this->matriceJeu[x_dest][y_dest-1], x_dest, y_dest-1);
                delete this->matriceJeu[x_dest][y_dest-1];
                this->matriceJeu[x_dest][y_dest-1] = NULL;
            }
            else {
                this->listePieceJB.remove(matriceJeu[x_dest][y_dest+1]);
                enregistrerDernierePieceCapturee(this->matriceJeu[x_dest][y_dest+1], x_dest, y_dest+1);
                delete this->matriceJeu[x_dest][y_dest+1];
                this->matriceJeu[x_dest][y_dest+1] = NULL;
            }

            deplacementAutorise = true;
            break;
        case PETIT_ROQUE:
            if (!simuler) {
                deplacerPiece(matriceJeu[7][p->getY()], 5, p->getY(), false);

                deplacementAutorise = true;
            }
            break;
        case GRAND_ROQUE:
            if (!simuler) {
                deplacerPiece(matriceJeu[0][p->getY()], 3, p->getY(), false);

                deplacementAutorise = true;
            }
            break;
        default:
            //cout << "Deplacement interdit !" << endl;
            //this->parent->SetPieceDeplacee(false);
            break;
    }

    if (deplacementAutorise) {
        // stockage du dernier "vrai" deplacement
        if (!simuler) {
            last_x_debut = p->getX();
            last_y_debut = p->getY();
            last_x_fin = x_dest;
            last_y_fin = y_dest;
            last_coup = matriceDepl[x_dest][y_dest];

            // nombres de coups et demi-coups
            nb_coups++;
            if (last_coup==CAPTURE || last_coup==PROMOTION_CAPTURE || last_coup==EN_PASSANT || p->getType()==PION)
                nb_demi_coups=0;
            else
                nb_demi_coups++;


            // permissions de roque
            if (p->getCouleur()==BLANC) {
                if (p->getType()==ROI) {
                    roquePB = false;
                    roqueGB = false;
                }
                else if (p->getType()==TOUR) {
                    if (p->getX()==0)
                        roqueGB = false;
                    else if (p->getX()==7)
                        roquePB = false;
                }
            }
            else {
                if (p->getType()==ROI) {
                    roquePN = false;
                    roqueGN = false;
                }
                else if (p->getType()==TOUR) {
                    if (p->getX()==0)
                        roqueGN = false;
                    else if (p->getX()==7)
                        roquePN = false;
                }
            }
        }

        Piece * p_dest = p;
        this->enregistrerDernierCoup(p_dest, p->getX(), p->getY());
        this->matriceJeu[p->getX()][p->getY()] = NULL;
        p_dest->setX(x_dest);
        p_dest->setY(y_dest);
        this->matriceJeu[x_dest][y_dest] = p_dest;
        this->parent->SetPieceDeplacee(true);
        if (!en_passant_active) {
            this->enPassantX = -10 ;
            this->enPassantY = -10 ;
        }
    }
    else {
        this->parent->SetPieceDeplacee(false);
    }

    if (simuler) {
        // RESTAURER ETAT
        restaurerEtat();
    }
}

void Partie::verifierPlateau() {
    bool echec = false;
    int deplacements_possibles = 0;

    cout << "verifierPlateau()" << endl;

    // On regarde si on a mis l'adversaire en échec

    // DEBUG DEBUG DEBUG
    if (verifierEchec(this->joueurActu)) {
	//if (verifierEchec(this->joueurActu==NOIR?BLANC:NOIR)) {
        echec = true;
	}

	// on regarde si l'adversaire peut se déplacer

    this->initialiserMatriceDepl();
    list<Piece *>::iterator it;
    // On regarde tous les mouvements possibles de toutes les pièces
    if (this->joueurActu == BLANC) {
    //if (this->joueurActu == NOIR) {
        for (it = listePieceJB.begin(); it != listePieceJB.end(); it++) {
            (*it)->calculDeplacements();
            //cout<<"Piece testee "<<" - "<<(*it)->getCode()<<"("<<(*it)->getX()<<"-"<<(*it)->getY()<<")"<<endl;

            for (int i=0; i<8; i++) {
                for (int j=0; j<8; j++) {
                    //cout<<"["<<i<<"-"<<j<<"]";
                    if ((this->matriceDepl[i][j] != AUCUN_COUP) && (this->matriceDepl[i][j] != CASE_ACTUELLE)) {
                        deplacements_possibles++;
                    }
                }
            }
            this->initialiserMatriceDepl();
        }
    }
    else {
        for (it = listePieceJN.begin(); it != listePieceJN.end(); it++) {
            (*it)->calculDeplacements();
            //cout<<"Piece testee "<<" - "<<(*it)->getCode()<<"("<<(*it)->getX()<<"-"<<(*it)->getY()<<")"<<endl;

            for (int i=0; i<8; i++) {
                for (int j=0; j<8; j++) {
                    //cout<<"["<<i<<"-"<<j<<"]";
                    if ((this->matriceDepl[i][j] != AUCUN_COUP) && (this->matriceDepl[i][j] != CASE_ACTUELLE)) {
                        deplacements_possibles++;
                    }
                }
            }
            this->initialiserMatriceDepl();
        }
    }


    if (echec) {
        if (deplacements_possibles == 0)
            cout << "ECHEC ET MAT : " << (this->joueurActu==NOIR?"noir":"blanc") << " a perdu !" << endl;//ECHEC ET MAT
        else {
            cout << "ECHEC : " << (this->joueurActu==NOIR?"noir":"blanc") << " est en echec !" << endl;//ECHEC
            Message msg(ECHEC);
            msg.ajouterChaine(this->joueurActu==NOIR?"noir":"blanc");
            parent->moteurGraphique->envoyerMessage(msg);
        }
    }
    else {
        if (deplacements_possibles == 0)
            cout << "PAT : " << (this->joueurActu==NOIR?"noir":"blanc") << " est pat !" << endl;//PAT
        else if (nb_demi_coups>=50) // DEBUG /!\ A MODIFIER ??? DOIT ETRE VALABLESI ECHEC OU PAT ???
            cout << "PARTIE NULLE : aucune capture ou mouvement de pion depuis 50 coups !" << endl;//NUL
        // CAS PARTICULIERS DE FIN DE PARTIE
        else if (   (listePieceJB.size()==1 && listePieceJN.size()==1) ||   // Roi contre Roi
                    (   (listePieceJB.size()==1 && listePieceJN.size()==2 && (getPieceN(0)->getType()==FOU || getPieceN(1)->getType()==FOU)) ||   // Roi contre Roi et Fou
                        (listePieceJN.size()==1 && listePieceJB.size()==2 && (getPieceB(0)->getType()==FOU || getPieceB(1)->getType()==FOU))      // Roi et Fou contre Roi
                    ) ||
                    (   (listePieceJB.size()==1 && listePieceJN.size()==2 && (getPieceN(0)->getType()==CAVALIER || getPieceN(1)->getType()==CAVALIER)) ||   // Roi contre Roi et Cavalier
                        (listePieceJN.size()==1 && listePieceJB.size()==2 && (getPieceB(0)->getType()==CAVALIER || getPieceB(1)->getType()==CAVALIER))      // Roi et Cavalier contre Roi
                    )
                )
            cout << "PARTIE NULLE : materiel insuffisant !" << endl;//NUL
        else if (   listePieceJB.size()==2 && listePieceJN.size()==2 &&     // Roi et Fou contre Roi et Fou avec les fous sur des couleurs différentes
                    (getPieceN(0)->getType()==FOU || getPieceN(1)->getType()==FOU) &&
                    (getPieceB(0)->getType()==FOU || getPieceB(1)->getType()==FOU)
                ) {
                    bool couleurdifferente;
                    if (getPieceN(0)->getType()==FOU) {
                        if (getPieceB(0)->getType()==FOU)
                            // (X+1)+(Y+1) --> pair=case noire, impair=case blanche
                            couleurdifferente = ((getPieceN(0)->getY()+1+getPieceN(0)->getX()+1) %2) != ((getPieceB(0)->getY()+1+getPieceB(0)->getX()+1) %2);
                        else
                            couleurdifferente = ((getPieceN(0)->getY()+1+getPieceN(0)->getX()+1) %2) != ((getPieceB(1)->getY()+1+getPieceB(1)->getX()+1) %2);
                    }
                    else {
                        if (getPieceB(0)->getType()==FOU)
                            couleurdifferente = ((getPieceN(1)->getY()+1+getPieceN(1)->getX()+1) %2) != ((getPieceB(0)->getY()+1+getPieceB(0)->getX()+1) %2);
                        else
                            couleurdifferente = ((getPieceN(1)->getY()+1+getPieceN(1)->getX()+1) %2) != ((getPieceB(1)->getY()+1+getPieceB(1)->getX()+1) %2);
                    }

                    if (couleurdifferente)  // Si les fous sont sur deux couleurs differentes
                        cout << "PARTIE NULLE : materiel insuffisant (2 rois et 2 fous incompatibles) !" << endl;//NUL
                }
        else
            ;//RIEN
    }
}

void Partie::initialiserMatriceDepl() {
    for (int i=0; i<8; i++) {
        for (int j=0; j<8; j++)
            this->matriceDepl[i][j] = AUCUN_COUP;
    }
}
bool Partie::verifierEchec(int joueurActu) {
    // SAUVER ETAT
    sauvegarderEtat();

	/* Recherche de la position du roi du joueur */
    list<Piece *>::iterator it;
	list<Piece *>::iterator itS;
	bool trouve = false;
	if (joueurActu == NOIR) { // Joueur Noir
		it = listePieceJN.begin();
        while(it != listePieceJN.end() && !trouve) {
			if ((*it)->getType() == ROI) {
				trouve = true;
                //cout<<"trouve";
			} else
				it++;
		}
		//cout<<(*it)->getX()<<" "<<(*it)->getY()<<endl;
		itS = listePieceJB.begin();
        //cout << listePieceJB.size();
        while(itS != listePieceJB.end()) {
            initialiserMatriceDepl();
            (*itS)->calculDeplacements(false);
			if (this->LireDepl((*it)->getX(),(*it)->getY()) == CAPTURE || this->LireDepl((*it)->getX(),(*it)->getY()) == PROMOTION_CAPTURE) {   // ou PROMOTION_CAPTURE
                // RESTAURER ETAT
		        restaurerEtat();
				return true;
			}
			itS++;
		}
		// RESTAURER ETAT
		restaurerEtat();
		return false;
    } else {
		it = listePieceJB.begin();
        while(it != listePieceJB.end() && !trouve) {
			if ((*it)->getType() == ROI)
				trouve = true;
			else
				it++;
		}
		//cout<<(*it)->getX()<<" "<<(*it)->getY()<<endl;
		itS = listePieceJN.begin();
        //cout << listePieceJN.size();
        while(itS != listePieceJN.end()) {
            initialiserMatriceDepl();
            (*itS)->calculDeplacements(false);
			//cout<<"("<<this->LireDepl((*it)->getX(),(*it)->getY())<<")"<<endl;
			if (this->LireDepl((*it)->getX(),(*it)->getY()) == CAPTURE || this->LireDepl((*it)->getX(),(*it)->getY()) == PROMOTION_CAPTURE) {   // ou PROMOTION_CAPTURE
                // RESTAURER ETAT
		        restaurerEtat();
				return true;
			}
			initialiserMatriceDepl();
			itS++;
		}

		// RESTAURER ETAT
		restaurerEtat();

		return false;
    }
}
void Partie::enregistrerDernierCoup(Piece * p, int x, int y) {
    // Enregistrement du déplacement
    // DEBUG
    piece_last = p;
    x_last = x;
    y_last = y;
}
void Partie::enregistrerDernierePieceCapturee(Piece * p, int x, int y) {
    switch (p->getType()) {
        case TOUR : // tour
            if (p->getCouleur() == NOIR)
                this->piece_capturee_last = new Tour(this, x, y, NOIR);
            else
                this->piece_capturee_last = new Tour(this, x, y, BLANC);
            break;
        case CAVALIER : // cavalier
            if (p->getCouleur() == NOIR)
                this->piece_capturee_last = new Cavalier(this, x, y, NOIR);
            else
                this->piece_capturee_last = new Cavalier(this, x, y, BLANC);
            break;
        case FOU : // fou
            if (p->getCouleur() == NOIR)
                this->piece_capturee_last = new Fou(this, x, y, NOIR);
            else
                this->piece_capturee_last = new Fou(this, x, y, BLANC);
            break;
        case REINE : // reine
            if (p->getCouleur() == NOIR) {
                this->piece_capturee_last = new Reine(this, x, y, NOIR);
                //cout<<"Reine noir recree a la case "<<x<<","<<y<<endl;
            } else {
                this->piece_capturee_last = new Reine(this, x, y, BLANC);
                //cout<<"Reine blanche recree a la case "<<x<<","<<y<<endl;
            }
            break;
        case PION : // pion
            if (p->getCouleur() == NOIR)
                this->piece_capturee_last = new Pion(this, x, y, NOIR);
            else
                this->piece_capturee_last = new Pion(this, x, y, BLANC);
            break;
    }
}
void Partie::annulerDeplacement() {
    // On redéplace la pièce à ses anciennes coordonnées
    //cout << "### " << piece_last << endl;

    if (piece_last != NULL) {
        //cout<<"<"<<piece_last->getType()<<">"<<x_last<<","<<y_last<<endl;
        //cout<<"depl "<<piece_last->getX()<<" - "<<piece_last->getY()<<endl;
        Piece * p_dest = this->piece_last;
        this->matriceJeu[piece_last->getX()][piece_last->getY()] = NULL;
        p_dest->setX(this->x_last);
        p_dest->setY(this->y_last);
        this->matriceJeu[this->x_last][this->y_last] = p_dest;
        //cout<<"ok"<<endl;
        //cout<<"Retablissement piece"<<endl;

        // On replace éventuellemnt la pièce qui a été capturée
        if (this->piece_capturee_last != NULL) {
            //cout<<"Retablissement piece capturee"<<endl;
            int x = this->piece_capturee_last->getX();
            int y = this->piece_capturee_last->getY();
            this->matriceJeu[x][y] = this->piece_capturee_last;
            //cout<<"Piece replacee ! : ("<<this->piece_capturee_last->getType()<<") -> "<<this->piece_capturee_last->getX()<<","<<this->piece_capturee_last->getY()<<endl;
            if (this->matriceJeu[x][y]->getCouleur() == NOIR)
                listePieceJN.push_back(matriceJeu[x][y]);
            else
                listePieceJB.push_back(matriceJeu[x][y]);
        }
        //this->piece_capturee_last = NULL;
    }
}

void Partie::sauvegarderEtat() {
    // Matrice de déplacement
	for (int i=0; i<8; i++) {
	   	for (int j=0; j<8; j++) {
	   	    sauv_matriceDepl[i][j] = this->matriceDepl[i][j];
	   	}
	}

    // En passant
    sauv_enPassantX = enPassantX;
    sauv_enPassantY = enPassantY;

    // Roques
    sauv_roquePB = roquePB;
    sauv_roqueGB = roqueGB;
    sauv_roquePN = roquePN;
    sauv_roqueGN = roqueGN;

    // moteurJeu
    sauv_pieceCliquee = parent->SiPieceCliquee();
    sauv_pieceDeplacee = parent->SiPieceDeplacee();
}

void Partie::restaurerEtat() {
    // Matrice de déplacement
    for (int i=0; i<8; i++) {
        for (int j=0; j<8; j++) {
            this->matriceDepl[i][j] = sauv_matriceDepl[i][j];
        }
    }

    // En passant
    enPassantX = sauv_enPassantX;
    enPassantY = sauv_enPassantY;

    // Roques
    roquePB = sauv_roquePB;
    roqueGB = sauv_roqueGB;
    roquePN = sauv_roquePN;
    roqueGN = sauv_roqueGN;

    // moteurJeu
    parent->SetPieceCliquee(sauv_pieceCliquee);
    parent->SetPieceDeplacee(sauv_pieceDeplacee);
}

void Partie::traiterPromotion(int type) {
    // SUPPRESSION DU PION
    if (joueurActu==NOIR)
        listePieceJN.remove(matriceJeu[promotionX][promotionY]);
    else
        listePieceJB.remove(matriceJeu[promotionX][promotionY]);
    delete matriceJeu[promotionX][promotionY];
    matriceJeu[promotionX][promotionY] = NULL;

    // CREATION DE LA NOUVELLE PIECE
    switch(type) {
        case REINE:
            matriceJeu[promotionX][promotionY] = new Reine(this, promotionX, promotionY, joueurActu);
            break;
        case FOU:
            matriceJeu[promotionX][promotionY] =  new Fou(this, promotionX, promotionY, joueurActu);
            break;
        case CAVALIER:
            matriceJeu[promotionX][promotionY] =  new Cavalier(this, promotionX, promotionY, joueurActu);
            break;
        case TOUR:
            matriceJeu[promotionX][promotionY] =  new Tour(this, promotionX, promotionY, joueurActu);
            break;
    }
    
    // AJOUT DE LA PIECE CHOISIE
    if (joueurActu==NOIR)
        listePieceJN.push_back(matriceJeu[promotionX][promotionY]);
    else
        listePieceJB.push_back(matriceJeu[promotionX][promotionY]);
        
    last_promo = (Type) type;
    parent->setAttentePromotion(false);
    finTour();
}

void Partie::finTour() {
    // l'échiquier à changé
    parent->moteurGraphique->envoyerMessage(Message(ECHIQUIER_MODIFIE));
    
    if (joueurActu==BLANC)
        jB->finTour();
    else
        jN->finTour();

    joueurActu = (joueurActu==BLANC?NOIR:BLANC);

    if (joueurActu==BLANC)
        jB->debutTour(last_x_debut, last_y_debut, last_x_fin, last_y_fin, last_coup, last_promo);
    else
        jN->debutTour(last_x_debut, last_y_debut, last_x_fin, last_y_fin, last_coup, last_promo);

    verifierPlateau();
}


Piece* Partie::LirePlateau(int x, int y) const {
    return this->matriceJeu[x][y];
}

Coup Partie::LireDepl(int x, int y) const {
    return this->matriceDepl[x][y];
}

void Partie::setPlateau(int x, int y, Piece * piece) {
    this->matriceJeu[x][y] = piece;
}

void Partie::setDepl(int x, int y, Coup coup) {
    this->matriceDepl[x][y] = coup;
}

int Partie::getEnPassantX() const {
    return enPassantX;
}

int Partie::getEnPassantY() const {
    return enPassantY;
}

bool Partie::getRoquePB() const {
    return roquePB;
}
bool Partie::getRoqueGB() const {
    return roqueGB;
}
bool Partie::getRoquePN() const {
    return roquePN;
}
bool Partie::getRoqueGN() const {
    return roqueGN;
}

int Partie::getNbCoups() const {
    return nb_coups;
}
int Partie::getNbDemiCoups() const {
    return nb_demi_coups;
}

Couleur Partie::getJoueurActu() const {
    return joueurActu;
}

Piece * Partie::getPieceN(int n) {
    list<Piece *>::iterator it;
    int i=0;
    for (it = listePieceJN.begin(); it != listePieceJN.end(); it++) {
        if (i==n)
            return (*it);
        i++;
    }

    return NULL;
}
Piece * Partie::getPieceB(int n) {
    list<Piece *>::iterator it;
    int i=0;
    for (it = listePieceJB.begin(); it != listePieceJB.end(); it++) {
        if (i==n)
            return (*it);
        i++;
    }

    return NULL;
}

